#include <stdio.h>
#include <stdlib.h>
#include <termios.h>
#include <unistd.h>
#include <fcntl.h>
#include <time.h>
#include <stdlib.h>

#define HEIGHT 10
#define WIDETH 20
#define MAX_LENGTH 50

enum MOVE_DIR {UP = -1,DOWN = 1,LEFT = 2,RIGHT = 4};

struct snake_node{
	int x;
	int y;
	enum MOVE_DIR dir;
}snake[MAX_LENGTH],food;

int snake_length = 3;
int score = 0;
int flag=0;
enum MOVE_DIR cur_dir = DOWN;

void init()
{
	int i;
	for(i=0;i<snake_length;i++)
	{
		snake[i].x=3;
		snake[i].y=3+i;
		snake[i].dir = RIGHT;
	}
	srand(time(NULL));
	food.x = rand()%(HEIGHT-2)+1;
	food.y = rand()%(WIDETH-2)+1;
}

void display()
{
	int i;
	char area[HEIGHT][WIDETH+2]={" __________________ \n",
		                  "|                  |\n",
			          "|                  |\n", 
				  "|                  |\n",
				  "|                  |\n",
				  "|                  |\n",
				  "|                  |\n",
				  "|                  |\n",
				  "|                  |\n",
				  "|__________________|\n"};
	for(i=0;i<snake_length;i++)
		area[ snake[i].x ][ snake[i].y ] = '*';
	area[ food.x ][ food.y ] = '#';
	system("clear");
	for(i=0;i<HEIGHT;i++)
		printf("%s",area[i]);
	printf("%d",score);
}

void snake_move()
{
	int i;
	struct snake_node head = snake[snake_length - 1];

	if(cur_dir == RIGHT ||	cur_dir == LEFT)
		head.y += (cur_dir-3);
	else
		head.x += cur_dir;
	if(head.x == food.x && head.y == food.y)
	{
		food.x = rand()%(HEIGHT-2)+1;
		food.y = rand()%(WIDETH-2)+1;
		head.dir = cur_dir;
		snake[snake_length] = head;
		snake_length++;
		score++;
	}
	else
	{
		for(i = 0;i<snake_length-1;i++)
			snake[i] = snake[i+1];
	}

	if(head.x > HEIGHT-1 || head.x < 1)
		flag=1;
	else if(head.y > WIDETH -2 || head.y < 1)
		flag=1;

	head.dir = cur_dir;
	snake[i] = head;
}

int keyboard()
{
	struct termios oldt,newt;
	int ch;
	int oldf;
	tcgetattr(STDIN_FILENO,&oldt);
	newt = oldt;
	newt.c_lflag &= ~(ICANON | ECHO);
	tcsetattr(STDIN_FILENO,TCSANOW,&newt);
	oldf = fcntl(STDIN_FILENO,F_GETFL,0);
	fcntl(STDIN_FILENO,F_SETFL, oldf | O_NONBLOCK);

	ch =getchar();

	tcsetattr(STDIN_FILENO,TCSANOW,&oldt);
	fcntl(STDIN_FILENO,F_SETFL,&oldf);

	if(ch != EOF)
		return ch;
	else
		return 0;
}

int main()
{
	int i,j;
	init();
	char ch;
	while(1)
	{
		switch(keyboard())
		{
			case 'w':cur_dir = UP;break;
			case 's':cur_dir = DOWN;break;
			case 'a':cur_dir = LEFT;break;
			case 'd':cur_dir = RIGHT;break;
		}
		snake_move();
		//food();
		//mark();
		if(flag)
			return 0;
		display();
		usleep(1000000/(score/10+1));
	}
	return 0;
}
